<template>
  <div class="app-container">
    <el-form :model="queryParams" ref="queryForm" size="small" :inline="true" v-show="showSearch" label-width="68px">

<el-form-item label="摄像头位置" prop="deviceId"> <!-- 修改label为摄像头位置 -->
    <el-select
      v-model="queryParams.deviceId"
      placeholder="请选择摄像头位置"
      clearable
    >
      <el-option
        v-for="device in deviceOptions"
        :key="device.sn"
        :label="device.location"
        :value="device.sn"
      />
    </el-select>
  </el-form-item>

      <el-form-item label="姓名" prop="name">
        <el-input
          v-model="queryParams.name"
          placeholder="请输入姓名"
          clearable
          @keyup.enter.native="handleQuery"
        />
      </el-form-item>
      <el-form-item label="人员类别" prop="category">
        <el-select v-model="queryParams.category" placeholder="请选择人员类别" clearable>
          <el-option
            v-for="dict in dict.type.category"
            :key="dict.value"
            :label="dict.label"
            :value="dict.value"
          />
        </el-select>
      </el-form-item>
      <el-form-item label="部门/职位" prop="department">
        <el-input
          v-model="queryParams.department"
          placeholder="请输入部门/职位"
          clearable
          @keyup.enter.native="handleQuery"
        />
      </el-form-item>
      <el-form-item label="手机号" prop="phone">
        <el-input
          v-model="queryParams.phone"
          placeholder="请输入手机号"
          clearable
          @keyup.enter.native="handleQuery"
        />
      </el-form-item>
      <el-form-item label="工号" prop="workId">
        <el-input
          v-model="queryParams.workId"
          placeholder="请输入工号"
          clearable
          @keyup.enter.native="handleQuery"
        />
      </el-form-item>
      <el-form-item label="最后出现时间" prop="lastAppearTime">
        <el-date-picker clearable
          v-model="queryParams.lastAppearTime"
          type="datetime"
          value-format="yyyy-MM-dd HH:mm:ss"
          placeholder="请选择最后出现时间">
        </el-date-picker>
      </el-form-item>
      <el-form-item>
        <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button>
        <el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
      </el-form-item>
    </el-form>

    <el-row :gutter="10" class="mb8">
      <el-col :span="1.5">
        <el-button
          type="primary"
          plain
          icon="el-icon-plus"
          size="mini"
          @click="handleAdd"
          v-hasPermi="['person:person:add']"
        >新增</el-button>
      </el-col>
      <el-col :span="1.5">
        <el-button
          type="success"
          plain
          icon="el-icon-edit"
          size="mini"
          :disabled="single"
          @click="handleUpdate"
          v-hasPermi="['person:person:edit']"
        >修改</el-button>
      </el-col>
      <el-col :span="1.5">
        <el-button
          type="danger"
          plain
          icon="el-icon-delete"
          size="mini"
          :disabled="multiple"
          @click="handleDelete"
          v-hasPermi="['person:person:remove']"
        >删除</el-button>
      </el-col>
      <el-col :span="1.5">
        <el-button
          type="warning"
          plain
          icon="el-icon-download"
          size="mini"
          @click="handleExport"
          v-hasPermi="['person:person:export']"
        >导出</el-button>
      </el-col>
            <!-- 同步按钮 -->
      <el-col :span="1.5">
        <el-button
          type="info"
          plain
          icon="el-icon-refresh"
          size="mini"
          @click="handleSync"
          v-hasPermi="['person:person:sync']"
        >同步</el-button>
      </el-col>
      <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
    </el-row>

    <el-table v-loading="loading" :data="personList" @selection-change="handleSelectionChange">
      <el-table-column type="selection" width="55" align="center" />
      <!-- <el-table-column label="主键" align="center" prop="id" /> -->
      <!-- <el-table-column label="设备端人员ID" align="center" prop="pid" /> -->
      <!-- <el-table-column label="摄像头位置" align="center" prop="deviceLocation" /> -->

      <el-table-column label="姓名" align="center" prop="name" />
      <el-table-column label="人员类别" align="center" prop="category">
        <template slot-scope="scope">
          <dict-tag :options="dict.type.category" :value="scope.row.category"/>
        </template>
      </el-table-column>
      <el-table-column label="性别" align="center" prop="gender">
        <template slot-scope="scope">
          <dict-tag :options="dict.type.gender" :value="scope.row.gender"/>
        </template>
      </el-table-column>
      <el-table-column label="年龄" align="center" prop="age" />
      <el-table-column label="部门/职位" align="center" prop="department" />
      <el-table-column label="工作状态" align="center" prop="workStatus">
        <template slot-scope="scope">
          <dict-tag :options="dict.type.work_status" :value="scope.row.workStatus"/>
        </template>
      </el-table-column>
      <el-table-column label="手机号" align="center" prop="phone" />
      <el-table-column label="身份证号" align="center" prop="idCardNo" />
      <el-table-column label="工号" align="center" prop="workId" />
      <el-table-column label="IC卡号" align="center" prop="icCardNo" />
      <el-table-column label="备注信息" align="center" prop="remark" />
      <el-table-column label="人员照片" align="center" prop="photo" width="100">
        <template slot-scope="scope">
          <image-preview :src="scope.row.photo" :width="50" :height="50"/>
        </template>
      </el-table-column>
      <el-table-column label="最后出现时间" align="center" prop="lastAppearTime" width="180">
        <template slot-scope="scope">
<span>{{ parseTime(scope.row.lastAppearTime, '{y}-{m}-{d} {h}:{i}:{s}') }}</span>
        </template>
      </el-table-column>
      <el-table-column label="操作" align="center" class-name="small-padding fixed-width">
        <template slot-scope="scope">
          <el-button
            size="mini"
            type="text"
            icon="el-icon-edit"
            @click="handleUpdate(scope.row)"
            v-hasPermi="['person:person:edit']"
          >修改</el-button>
          <el-button
            size="mini"
            type="text"
            icon="el-icon-delete"
            @click="handleDelete(scope.row)"
            v-hasPermi="['person:person:remove']"
          >删除</el-button>
        </template>
      </el-table-column>
    </el-table>

    <pagination
      v-show="total>0"
      :total="total"
      :page.sync="queryParams.pageNum"
      :limit.sync="queryParams.pageSize"
      @pagination="getList"
    />
       <!-- 修改后的对话框 -->
  <el-dialog
    :title="title"
    :visible.sync="open"
    width="800px"
    append-to-body
    :close-on-click-modal="false"
  >
      <el-form ref="form" :model="form" :rules="rules" label-width="100px">
      <el-row :gutter="20"> <!-- 使用栅格布局 -->
        <!-- 左列 -->
        <el-col :span="12">

<el-form-item label="摄像头位置" prop="deviceIds">
  <el-select
    v-model="form.deviceIds"
    multiple
    filterable
    default-first--option
    placeholder="请选择摄像头位置（可多选）"
  >
    <el-option
      v-for="device in deviceOptions"
      :key="device.sn"
      :label="device.location"
      :value="device.sn"
    />
  </el-select>
</el-form-item>
        <el-form-item label="姓名" prop="name">
          <el-input v-model="form.name" placeholder="请输入姓名" />
        </el-form-item>
        <el-form-item label="人员类别" prop="category">
          <el-select v-model="form.category" placeholder="请选择人员类别">
            <el-option
              v-for="dict in dict.type.category"
              :key="dict.value"
              :label="dict.label"
              :value="parseInt(dict.value)"
            ></el-option>
          </el-select>
        </el-form-item>

          <el-form-item label="性别" prop="gender">
            <el-radio-group v-model="form.gender">
              <el-radio
                v-for="dict in dict.type.gender"
                :key="dict.value"
                :label="parseInt(dict.value)"
              >{{dict.label}}</el-radio>
            </el-radio-group>
          </el-form-item>

        <el-form-item label="年龄" prop="age">
          <el-select v-model="form.age" placeholder="请选择年龄">
            <el-option
              v-for="age in ageOptions"
              :key="age"
              :label="age"
              :value="age">
            </el-option>
          </el-select>
        </el-form-item>
        <el-form-item label="部门/职位" prop="department">
          <el-input v-model="form.department" placeholder="请输入部门/职位" />
        </el-form-item>
                </el-col>
                <!-- 右列 -->
        <el-col :span="12">
        <el-form-item label="手机号" prop="phone">
          <el-input v-model="form.phone" placeholder="请输入手机号" />
        </el-form-item>
        <el-form-item label="身份证号" prop="idCardNo">
          <el-input v-model="form.idCardNo" placeholder="请输入身份证号" />
        </el-form-item>
        <el-form-item label="工号" prop="workId">
          <el-input v-model="form.workId" placeholder="请输入工号" />
        </el-form-item>
        <el-form-item label="IC卡号" prop="icCardNo">
          <el-input v-model="form.icCardNo" placeholder="请输入IC卡号" />
        </el-form-item>
        <el-form-item label="备注信息" prop="remark">
          <el-input v-model="form.remark" placeholder="请输入备注信息" />
        </el-form-item>
        <el-form-item label="人员照片" prop="photo">
          <image-upload v-model="form.photo"
                    :limit="1"
          />
        </el-form-item>
        <el-form-item label="最后出现时间" prop="lastAppearTime">
          <el-date-picker clearable
            v-model="form.lastAppearTime"
          type="datetime"
          value-format="yyyy-MM-dd HH:mm:ss"
            placeholder="请选择最后出现时间">
          </el-date-picker>
        </el-form-item>
        </el-col>
        </el-row>
      </el-form>

      <div slot="footer" class="dialog-footer">
        <el-button type="primary" @click="submitForm">确 定</el-button>
        <el-button @click="cancel">取 消</el-button>
      </div>
    </el-dialog>

        <!-- 新增设备选择对话框 -->
  <el-dialog
    title="选择同步设备"
    :visible.sync="syncDialogVisible"
    width="30%"
    append-to-body
  >
    <el-select
  v-model="sns"
  multiple
  placeholder="请选择摄像头位置（可多选）"
  style="width:100%"
>
  <el-option
    v-for="device in deviceOptions"
    :key="device.sn"
    :label="device.location"
    :value="device.sn"
  />
    </el-select>
    <span slot="footer">
      <el-button @click="syncDialogVisible = false">取消</el-button>
      <el-button type="primary" @click="confirmSync">开始同步</el-button>
    </span>
  </el-dialog>

  </div>

</template>

<script>
import { listPerson, getPerson, delPerson, addPerson, updatePerson, syncFromCameraServer } from "@/api/student/person/person";
import { listDevice } from "@/api/student/device/device"; // 新增设备API导入

export default {
  name: "Person",
  dicts: ['work_status', 'category', 'gender', 'del_flag'],
  data() {
    return {
      syncDialogVisible: false, // 控制设备选择对话框
      sn: null, // 选中的设备SN
      sns: [],    // 选中的设备SN列表
      // 遮罩层
      loading: true,
      // 选中数组
      ids: [],
      // 非单个禁用
      single: true,
      // 非多个禁用
      multiple: true,
      // 显示搜索条件
      showSearch: true,
      // 总条数
      total: 0,
      // 人员信息表格数据
      personList: [],
      // 弹出层标题
      title: "",
      // 是否显示弹出层
      open: false,
      // 查询参数
      queryParams: {
        pageNum: 1,
        pageSize: 10,
        deviceId: null,
        name: null,
        category: null,
        department: null,
        phone: null,
        workId: null,
        lastAppearTime: null,
        studentId: null, // 新增学生学号字段
        classes: null,
      },
      // 表单参数
      form: {
        deviceIds: [],
      },
      // 表单校验
      rules: {
        deviceIds: [
          { required: true, message: "请至少选择一个设备", trigger: "change" },
          { type: 'array', min: 1, message: '请至少选择一个设备', trigger: 'change' }
        ],
        name: [
          { required: true, message: "姓名不能为空", trigger: "blur" }
        ],
        category: [
          { required: true, message: "人员类别不能为空", trigger: "change" }
        ],
        gender: [
          { required: true, message: "性别不能为空", trigger: "change" }
        ],
        photo: [
          { required: true, message: "人员照片不能为空", trigger: "change" }
        ],
        age: [
          { required: true, message: "请选择年龄", trigger: "change" }
        ]
      },
      // 新增设备选项
      deviceOptions: [],
      ageOptions: [],
    };
  },
  created() {
    this.getList();
    this.getDeviceList(); // 新增：加载设备列表
    this.generateAgeOptions(); // 新增：生成年龄选项
  },
  methods: {
    // 新增：获取设备列表
    getDeviceList() {
      listDevice({
        pageNum: 1,
        pageSize: 1000 // 获取足够多的设备
      }).then(response => {
        this.deviceOptions = response.rows;
      });
    },
 /** 修改后的同步按钮点击事件 */
    handleSync() {
      this.sn = null;
      this.syncDialogVisible = true;
    },

    /** 确认同步操作 */
confirmSync() {
  // 1. 检查设备选择数组而不是单个设备
  if (this.sns.length === 0) {
    this.$modal.msgWarning("请至少选择一个设备");
    return;
  }

  this.syncDialogVisible = false;

  // 2. 构建设备名称列表
  const deviceNames = this.sns.map(sn => this.getDeviceLocation(sn)).join('、');

  this.$modal.confirm(`确认同步以下设备的人员数据? ${deviceNames}`).then(() => {
    this.$modal.loading("正在同步人员数据，请稍后...");

    // 3. 为每个设备创建同步请求
    const requests = this.sns.map(sn =>
      syncFromCameraServer(sn).catch(error => {
        return {sn, error: error.message};  // 捕获错误并返回设备信息
      })
    );

    // 4. 执行所有请求
    Promise.all(requests).then(results => {
      this.$modal.closeLoading();

      // 5. 处理结果
      const success = results.filter(res => !res.error);
      const failed = results.filter(res => res.error);

      if (failed.length === 0) {
        this.$modal.msgSuccess(`同步成功: ${success.length}个设备`);
      } else {
        const errors = failed.map(f =>
          `${this.getDeviceLocation(f.sn)}: ${f.error}`
        ).join('<br/>');

        this.$modal.msgError(`部分同步失败:<br/>${errors}`, {
          dangerouslyUseHTMLString: true,
          duration: 10000
        });
      }

      this.getList();  // 刷新列表
    });
  }).catch(() => { /* 用户取消操作 */ });
},

    /** 根据SN获取设备位置 */
    getDeviceLocation(sn) {
      const device = this.deviceOptions.find(d => d.sn === sn);
      return device ? device.location : "未知设备";
    },
  // 添加日期格式化方法
  formatDate(date) {
    const pad = num => num.toString().padStart(2, '0');
    return `${date.getFullYear()}-${pad(date.getMonth()+1)}-${pad(date.getDate())} ${
      pad(date.getHours())}:${pad(date.getMinutes())}:${pad(date.getSeconds())}`;
  },

  parseDateString(dateString) {
    if (!dateString) return null;
    // 尝试解析各种格式的日期
    const date = new Date(dateString);
    if (isNaN(date.getTime())) {
      // 尝试解析自定义格式
      const match = dateString.match(/(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})/);
      if (match) {
        return new Date(
          parseInt(match[1]),
          parseInt(match[2]) - 1,
          parseInt(match[3]),
          parseInt(match[4]),
          parseInt(match[5]),
          parseInt(match[6])
        );
      }
      return null;
    }
    return date;
  },


    /** 查询人员信息列表 */
    getList() {
      this.loading = true;
      listPerson(this.queryParams).then(response => {
         this.personList = response.rows.map(person => {
      // 将SN转换为位置名称
      const device = this.deviceOptions.find(d => d.sn === person.deviceId);
      return {
        ...person,
        deviceLocation: device ? device.location : "未知位置" // 新增映射字段
      };
    });
        this.total = response.total;
        this.loading = false;
      });
    },
    // 取消按钮
    cancel() {
      this.open = false;
      this.reset();
    },
    // 表单重置
    reset() {
      this.form = {
        id: null,
        pid: null,
        deviceId: null,
        name: null,
        category: null,
        gender: null,
        age: null,
        department: null,
        workStatus: null,
        phone: null,
        idCardNo: null,
        workId: null,
        icCardNo: null,
        remark: null,
        photo: null,
        lastAppearTime: null,
        createBy: null,
        createTime: null,
        updateBy: null,
        updateTime: null,
        delFlag: null
      };
      this.resetForm("form");
    },
    /** 搜索按钮操作 */
    handleQuery() {
      this.queryParams.pageNum = 1;
      this.getList();
    },
    /** 重置按钮操作 */
    resetQuery() {
      this.resetForm("queryForm");
      this.handleQuery();
    },
    // 多选框选中数据
    handleSelectionChange(selection) {
      this.ids = selection.map(item => item.id)
      this.single = selection.length!==1
      this.multiple = !selection.length
    },
    /** 新增按钮操作 */
    handleAdd() {
      this.reset();
      this.open = true;
      this.title = "添加人员信息";
    },
    /** 修改按钮操作 */
    handleUpdate(row) {
      this.reset();
      const id = row.id || this.ids;
      getPerson(id).then(response => {
        this.form = response.data;

        // 确保deviceIds是数组
        if (!this.form.deviceIds) {
          this.form.deviceIds = [];
        }

        // 转换时间字符串为 Date 对象
        if (this.form.lastAppearTime) {
          this.form.lastAppearTime = this.parseDateString(this.form.lastAppearTime);
        }

        this.open = true;
        this.title = "修改人员信息";
      }).catch(error => {
        console.error("获取人员信息失败", error);
        this.$modal.msgError("获取人员信息失败");
      });
    },

    /** 提交按钮 */
    submitForm() {
  this.$refs["form"].validate(valid => {
    if (valid) {
      // 再次确认设备选择不为空
      if (!this.form.deviceIds || this.form.deviceIds.length === 0) {
        this.$modal.msgWarning("请至少选择一个设备");
        return;
      }

      // 克隆表单数据，避免修改原始数据
      const formData = JSON.parse(JSON.stringify(this.form));

      // 转换日期格式为后端期望的格式
      if (formData.lastAppearTime instanceof Date) {
        formData.lastAppearTime = this.formatDate(formData.lastAppearTime);
      }

      // 添加日期格式化方法
      if (typeof this.formatDate !== 'function') {
        this.formatDate = function(date) {
          const pad = num => num.toString().padStart(2, '0');
          return `${date.getFullYear()}-${pad(date.getMonth()+1)}-${pad(date.getDate())} ${
            pad(date.getHours())}:${pad(date.getMinutes())}:${pad(date.getSeconds())}`;
        }
      }

      if (this.form.id != null) {
        updatePerson(formData).then(response => {
          this.$modal.msgSuccess("修改成功");
          this.open = false;
          this.getList();
        }).catch(error => {
          console.error("修改失败", error);
          // 特殊处理设备为空的错误
          if (error.response && error.response.data && error.response.data.msg.includes("请至少选择一个设备")) {
            this.$modal.msgWarning("请至少选择一个设备");
          } else {
            this.$modal.msgError("修改失败: " + (error.response?.data?.msg || error.message || "未知错误"));
          }
        });
      } else {
        addPerson(formData).then(response => {
          this.$modal.msgSuccess("新增成功");
          this.open = false;
          this.getList();
        }).catch(error => {
          console.error("新增失败", error);
          // 特殊处理设备为空的错误
          if (error.response && error.response.data && error.response.data.msg.includes("请至少选择一个设备")) {
            this.$modal.msgWarning("请至少选择一个设备");
          } else {
            this.$modal.msgError("新增失败: " + (error.response?.data?.msg || error.message || "未知错误"));
          }
        });
      }
    }
  });
},
    /** 删除按钮操作 */
    handleDelete(row) {
      const ids = row.id || this.ids;
      this.$modal.confirm('是否确认删除人员信息编号为"' + ids + '"的数据项？').then(function() {
        return delPerson(ids);
      }).then(() => {
        this.getList();
        this.$modal.msgSuccess("删除成功");
      }).catch(() => {});
    },
    /** 导出按钮操作 */
    handleExport() {
      this.download('student/person/person/export', {
        ...this.queryParams
      }, `person_${new Date().getTime()}.xlsx`)
    },
    generateAgeOptions() {
      const ages = [];
      for (let i = 1; i <= 100; i++) {
        ages.push(i);
      }
      this.ageOptions = ages;
    }
  }
};
</script>
<style scoped>
/* 添加间距优化 */
.el-form-item {
  margin-bottom: 18px;
}
</style>
